/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package encaps.entities;

import java.io.UnsupportedEncodingException;
import java.security.NoSuchAlgorithmException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Collection;
import java.util.HashMap;
import java.util.LinkedList;
import javax.ejb.CreateException;
import javax.sql.DataSource;
import javax.ejb.EJBException;
import javax.ejb.EntityBean;
import javax.ejb.EntityContext;
import javax.ejb.FinderException;
import javax.ejb.NoSuchEntityException;
import javax.ejb.ObjectNotFoundException;
import javax.ejb.RemoveException;
import javax.naming.NamingException;
import encaps.utils.MD5Hash;
import encaps.utils.DatabaseUtil;
import encaps.utils.StringUtil;


public class User implements EntityBean {

    public static final String TABLE_NAME = "User";
    public static final String LOGIN = "login";
    public static final String PIC = "pic";
    public static final String PASS = "pass";
    public static final String INFO = "info";
    public static final String ROLE = "role";
    public static final String EMAIL = "email";
    public static final String CONTACTS = "contacts";
    private EntityContext context;
    private DataSource dataSource;
    private boolean isEdited;
    private Long id;
    private String login;
    private String pic;
    private String info;
    private String role;
    private String email;
    private String contacts;
    private String pass;

    
    public void setEntityContext(EntityContext aContext) {
        context = aContext;
        try {
            dataSource = DatabaseUtil.getDataSource();
            isEdited = false;
        } catch (NamingException e) {
            throw new EJBException("DataSource lookup error", e);
        }
    }

    public Long ejbCreate(String login, String avatar, String info, String contacts,
             String password, String email, String role) throws CreateException {
        PreparedStatement insertValuesQuery = null;
        PreparedStatement selectIdQuery = null;
        Connection conn = null;
        try {
            this.pic = avatar;
            this.login = login;
            this.info = info;
            this.contacts = contacts;
            this.pass = password;
            this.email = email;


            conn = dataSource.getConnection();
            insertValuesQuery = conn.prepareStatement("INSERT INTO user(login,pass, info, role, email, contacts) VALUES(?, ?, ?, ?, ?, ?)");
            insertValuesQuery.setString(1, login);
            insertValuesQuery.setString(2, pass);
            insertValuesQuery.setString(3, info);
            //insertValuesQuery.setString(4, "ff"role);
            insertValuesQuery.setString(5, email);
            insertValuesQuery.setString(6, contacts);


            if (insertValuesQuery.executeUpdate() != 1) {
                throw new CreateException("Insertion error");
            }
            selectIdQuery = conn.prepareStatement("SELECT LAST_INSERT_ID()");
            ResultSet rs = selectIdQuery.executeQuery();
            if (!rs.next()) {
                throw new CreateException("Insertion error");
            }
            id = rs.getLong(1);

            isEdited = false;
            return id;
        } catch (Exception ex) {
            throw new EJBException("Error in User.ejbCreate method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, selectIdQuery);
            DatabaseUtil.closeConnection(null, insertValuesQuery);
        }

    }

    public void ejbPostCreate(String login, String avatar, String info, String contacts,
             String password, String email, String role) throws CreateException {

    }

    
    //привет лунатикам
    public void ejbActivate() {
    }

    
    public void ejbPassivate() {
    }

    
    public void ejbRemove() throws RemoveException {
        PreparedStatement ps = null;
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
            ps = conn.prepareStatement("DELETE FROM user WHERE id=?");
            ps.setLong(1, id);
            if(ps.executeUpdate() < 1) {
                throw new RemoveException("Deletion error. Id="+id);
            }
            isEdited = false;
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbRemove method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }

    
    public void unsetEntityContext() {
        context = null;
    }

    
    public void ejbLoad() {
        id = (Long) context.getPrimaryKey();
        PreparedStatement ps = null;
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
            ps = conn.prepareStatement("SELECT login, pass, pic, info, role, email, contacts FROM user WHERE id=?");
            ps.setLong(1, id);
            ResultSet rs = ps.executeQuery();
            if(!rs.next()) {
                throw new NoSuchEntityException("No user found by id = " + id);
            }
            login = rs.getString(LOGIN);
            pass = rs.getString(PASS);
            pic = rs.getString(PIC);
            info = rs.getString(INFO);
            role = rs.getString(ROLE);
            email = rs.getString(EMAIL);
            contacts = rs.getString(CONTACTS);
            
            isEdited = false;
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbLoad method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }

   
    public void ejbStore() {
        if(!isEdited) {
            return;
        }
        PreparedStatement ps = null;
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
            ps = conn.prepareStatement("UPDATE user SET login=?,pass=?, pic=?, info=?, role=?, email=?, contacts=? WHERE id=?");
            ps.setString(1, login);
            ps.setString(2, pass);
            ps.setString(3, pic);
            ps.setString(4, info);
            ps.setString(5, role);
            ps.setString(6, email);
            ps.setString(7, contacts);
            ps.setLong(8, id);
            if(ps.executeUpdate() < 1) {
                throw new NoSuchEntityException("No user found by id = " + id);
            }
            isEdited = false;
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbStore method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }

    
    public java.lang.Long ejbFindByPrimaryKey(Long key) throws FinderException {
        PreparedStatement ps = null;
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
            ps = conn.prepareStatement("SELECT id FROM user WHERE id=?;");
            ps.setLong(1, key);
            ResultSet rs = ps.executeQuery();
            if(!rs.next()) {
                throw new ObjectNotFoundException("No user found by primary key = " + key);
            }
            return key;
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbFindByPrimaryKey method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }
    
    public Long ejbFindByLogin(String login) throws FinderException {
        /*HashMap criteria = new HashMap();
        if(!StringUtil.isEmpty(login)) criteria.put(LOGIN, login);
        if(criteria.isEmpty()) {
            throw new FinderException("User search criteria is empty");
        }*/

        PreparedStatement ps = null;
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
            //String searchQuery = StringUtil.constructSelectQuery(TABLE_NAME, "id", criteria);
            //System.out.println("s q:" + searchQuery);
            ps = conn.prepareStatement("SELECT id FROM user WHERE login=?");
            ps.setString(1, login);
            ResultSet rs = ps.executeQuery();
            if(!rs.next()) {
                throw new ObjectNotFoundException("No user found by login = " + login);
            }
            return rs.getLong(1);
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbFindByLogin method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }
    
    public Collection ejbFindAll() {
        PreparedStatement ps = null;
        Connection conn = null;
        
        try {
            conn = dataSource.getConnection();
            ps = conn.prepareStatement("SELECT id FROM User");
            Collection keys = new LinkedList();
            ResultSet rs = ps.executeQuery();
            while(rs.next()) {
                keys.add(rs.getLong(1));
            }
            return keys;
        } catch(SQLException ex) {
            throw new EJBException("Error in User.ejbFindAll method", ex);
        } finally {
            DatabaseUtil.closeConnection(conn, ps);
        }
    }

    public Long getID()
    {
        return id;
    }
    public String getLogin()
    {
        return login;
    }
    public void setLogin(String value)
    {
        this.login = value;
        isEdited = true;
    }
    public String getAvatar()
    {
        return pic;
    }
    public void setAvatar(String value)
    {
        this.pic = value;
        isEdited = true;
    }
    public String getInfo()
    {
        return info;
    }
    public void setInfo(String value)
    {
        this.info = value;
        isEdited = true;
    }
    public String getRole()
    {
        return role;
    }
    public void setRole(String value)
    {
        this.role = value;
        isEdited = true;
    }
    public void setRole(Role r)
    {
        this.role = r.getRoleName();
        isEdited = true;
    }
    public String getEmail()
    {
        return email;
    }
    public void setEmail(String value)
    {
        this.email = value;
        isEdited = true;
    }
    public String getContacts()
    {
        return contacts;
    }
    public void setContacts(String value)
    {
        this.contacts = value;
        isEdited = true;
        
    }
    public String getPassword()
    {
        return pass;
    }
    public void setPassword(String value) throws NoSuchAlgorithmException,
         UnsupportedEncodingException 
    {
        this.pass = MD5Hash.getHash(value);
        isEdited = true;
    }
    
    // </editor-fold>
}
